<template>
  <div class="container">
    <el-row>
      <el-col :span="0">

      </el-col>
      <el-col :span="24">
         <!-- 配置区 -->
        <div>
            <el-form :inline="true" style="float: left;">
              <el-form-item style="float: left;" label="分析事件">
                <el-select  v-model="form.event" placeholder="请选择" style="min-width: 150px;">
                  <el-option v-for="event in events"  :value="event.id" :label="event.name">{{ event.name }}</el-option>
              </el-select>
              </el-form-item>
              <el-form-item style="float: left;" label="分析状态">
                <el-select  v-model="form.status" placeholder="请选择" style="min-width: 150px;">
                  <el-option v-for="status in statuss"  :value="status.id" :label="status.name">{{ status.name }}</el-option>
              </el-select>
              </el-form-item>
              <el-form-item>
                <el-button @click="handleExecute" type="primary">执行</el-button>
                  <el-button @click="handleClear" type="danger">清空</el-button>
              </el-form-item>
            </el-form>
        </div>
        <!-- 树状图展示 -->
        <div ref="graphContainer" class="graph-container" id="container"></div>
      </el-col>
    </el-row>
   
  </div>
</template>
<script setup lang="ts">
import { ref, reactive, onMounted } from 'vue';
import { Graph } from '@antv/x6';
import { stroke } from '@antv/x6/lib/registry/highlighter/stroke';
import { center } from '@antv/x6/lib/registry/node-anchor/bbox';
import { ElMessage } from 'element-plus';


const form = reactive<any>({
  event:'eventA',
  status:1,
});
// 事件配置
const events = reactive([
  { id: 'eventA', name: '事件A', status: '空' },
  { id: 'eventB', name: '事件B', status: '空' },
  { id: 'eventC', name: '事件C', status: '空' },
  { id: 'eventD', name: '事件D', status: '空' },
  { id: 'eventE', name: '事件E', status: '空' },
  { id: 'eventF', name: '事件F', status: '空' },
  { id: 'eventG', name: '事件G', status: '空' },
]);
const statuss = reactive([
  { id: 1, name: '存在',  },
  { id: 2, name: '不存在',  },
  { id: 3, name: '空',  },
]);

// 树状图实例
const graph = ref<any>(null);

// 初始化树状图
const initGraph = () => {
  if (!graph.value) {
    graph.value = new Graph({
      container: document.getElementById('container') as HTMLElement,
      background: {
        color: '#F2F7FA',
      },
      grid: {
        visible: true,
      },
      width: 800,
      height: 600,
    });
  }
};

// 根据配置更新树状图
const addNodes = () => {
  // 重新绘制树状图

  graph.value.addNode({
    id: 'eventA',
    shape: 'rect',
    label: '事件A',
    x: 310,
    y: 0,
    width: 100,
    height: 60,
  });
  graph.value.addNode({
    id: 'eventB',
    shape: 'circle',
    label: '事件B',
    x: 200,
    y: 290,
    width: 60,
    height: 60,
  });
  graph.value.addNode({
    id: 'eventC',
    shape: 'circle',
    label: '事件C',
    x: 480,
    y: 290,
    width: 60,
    height: 60,
  });
  graph.value.addNode({
    id: 'eventD',
    shape: 'circle',
    label: '事件D',
    x: 150,
    y: 530,
    width: 60,
    height: 60,
  });
  graph.value.addNode({
    id: 'eventE',
    shape: 'circle',
    label: '事件E',
    x: 260,
    y: 530,
    width: 60,
    height: 60,
  });
  graph.value.addNode({
    id: 'eventF',
    shape: 'circle',
    label: '事件F',
    x: 400,
    y: 530,
    width: 60,
    height: 60,
  });
  graph.value.addNode({
    id: 'eventG',
    shape: 'circle',
    label: '事件G',
    x: 560,
    y: 530,
    width: 60,
    height: 60,
  });

  
  graph.value.addNode({
    id: 'and',
    shape: 'polygon',
    x: 330,
    y: 150,
    width: 60,
    height: 75,
    label: '&',
    attrs: {
      body: {
        fill: '#409eff',
        stroke: '#fff',
        // 指定 refPoints 属性，多边形顶点随图形大小自动缩放
        // https://x6.antv.vision/zh/docs/api/registry/attr#refpointsresetoffset
        refPoints: '0 5, 5 0, 10 5, 10 10,0 10',
      },
      label: {
        text: '+',
        fill: '#fff',
        fontSize: 53,
        refY: 50,
      },
    },
  });
  
  graph.value.addNode({
    id: 'and1',
    shape: 'polygon',
    x: 200,
    y: 390,
    width: 60,
    height: 75,
    label: '&',
    attrs: {
      body: {
        fill: '#409eff',
        stroke: '#fff',
        // 指定 refPoints 属性，多边形顶点随图形大小自动缩放
        // https://x6.antv.vision/zh/docs/api/registry/attr#refpointsresetoffset
        refPoints: '0 5, 5 0, 10 5, 10 10,0 10',
      },
      label: {
        text: '与门',
        fill: '#fff',
        fontSize: 13,
        refY: 50,
      },
    },
  });
  graph.value.addNode({
    id: 'and2',
    shape: 'polygon',
    x: 480,
    y: 410,
    width: 60,
    height: 75,
    label: '||',
    attrs: {
      body: {
        fill: '#409eff',
        stroke: '#fff',
        // 指定 refPoints 属性，多边形顶点随图形大小自动缩放
        // https://x6.antv.vision/zh/docs/api/registry/attr#refpointsresetoffset
        refPoints: '0 5, 5 0, 10 5, 10 10,0 10',
      },
      label: {
        text: '或门',
        fill: '#fff',
        fontSize: 13,
        refY: 50,
      },
    },
  });

  graph.value.addEdge({
      source: 'eventA',
      target: 'and',
  });
  graph.value.addEdge({
      source: 'and',
    target: 'eventB',
  });
  graph.value.addEdge({
      source: 'eventB',
    target: 'and1',
  });
  graph.value.addEdge({
      source: 'and1',
    target: 'eventD',
  });
  graph.value.addEdge({
      source: 'and1',
    target: 'eventE',
  });

  graph.value.addEdge({
      source: 'eventC',
    target: 'and2',
  });
  graph.value.addEdge({
      source: 'and2',
    target: 'eventF',
  });
  graph.value.addEdge({
      source: 'and2',
    target: 'eventG',
  });
 
  



  graph.value.addEdge({
      source: 'and',
    target: 'eventC',
  });
 
};

// 改变颜色
const updateGraph = () => {
/**
 * @description 处理事件存在的情况
 * @param id 事件id
 */  
  const handelData1 = (id:string) => {
    const node = graph.value.getCellById(id);
    const outgoingEdges = graph.value.getOutgoingEdges(node);
    if(!outgoingEdges) return
    const nextNodes = outgoingEdges.map((edge:any) => edge.getTargetCell());
    const nextNode = nextNodes[0]; // 当前为逻辑关系 与门或者或门·
    const label = nextNode.label; //逻辑门的label
    const node2 = graph.value.getCellById(nextNode.id);
    const outgoingEdges2 = graph.value.getOutgoingEdges(node2);
    //拿到关联的事件
    const nextNodes2 = outgoingEdges2.map((edge:any) => edge.getTargetCell());
    if(nextNodes2.length === 0){
      return;
    }
    if(label === '&') {
      nextNodes2.forEach((node:any) => {
          node.setAttrs ({
            body: {
              fill: getFillColor("存在"),
            },
            value:"存在"
          })
          console.log(`分析出：【${node.label}】状态存在`)
      });
      
    }else if(label === '||' && nextNodes2.length === 1) {
      nextNodes2.forEach((node:any) => {
          node.setAttrs ({
            body: {
              fill: getFillColor("存在"),
            },
            value:"存在"
          })
      });
      console.log(`分析出：【${node.label}】状态存在`)
    }else if(label === '||' && nextNodes2.length > 1) {
      nextNodes2.forEach((node:any) => {
          node.setAttrs ({
            body: {
              fill: getFillColor("空"),
            },
            value:"空"
          })
      });
      console.log(`无法分析出【${node.label}】的子节点状态，可选择其他节点继续分析`)
    }
    nextNodes2.forEach((node:any) => {
      handelData1(node.id)
    })
  }
  /**
 * @description 处理事件不存在的情况
 * @param id 事件id
 */  
 const handelData2 = (id:string) => {
    const node = graph.value.getCellById(id);
    const outgoingEdges = graph.value.getOutgoingEdges(node);
    if(!outgoingEdges) return
    const nextNodes = outgoingEdges.map((edge:any) => edge.getTargetCell());
    const nextNode = nextNodes[0]; // 当前为逻辑关系 与门或者或门·
    const label = nextNode.label; //逻辑门的label
    const node2 = graph.value.getCellById(nextNode.id);
    const outgoingEdges2 = graph.value.getOutgoingEdges(node2);
    //拿到关联的事件
    const nextNodes2 = outgoingEdges2.map((edge:any) => edge.getTargetCell());
    if(nextNodes2.length === 0){
      return;
    }
      nextNodes2.forEach((node:any) => {
          node.setAttrs ({
            body: {
              fill: getFillColor("空"),
            },
            value:"空"
          })
          console.log(`无法分析出【${node.label}】节点的状态，可选择其他节点继续分析`)
      });
      
    nextNodes2.forEach((node:any) => {
      handelData2(node.id)
    })
  }
  /**
   * @description 根据状态更新颜色
   */
  switch (form.status) {
    case 1:
      handelData1(form.event);
      break;
    case 2:
      handelData2(form.event);
      break;
    case 3:
    handelData2(form.event);
      break;
    default:
      break;
  }
}
// 获取填充颜色
const getFillColor = (status: string) => {
  switch (status) {
    case '存在':
      return '#ff0000'; // 红色
    case '不存在':
      return '#00ff00'; // 绿色
    default:
      return '#ffffff'; // 默认白色
  }
};
const  handleP = () => {
  console.log(  graph.value.toJSON());
}

// 执行按钮点击事件
const handleExecute = () => {
  updateGraph();
};

// 清空按钮点击事件
const handleClear = () => {
  events.forEach(event => {
    event.status = '空';
  });
  updateGraph();
};

onMounted(() => {
 // 初始化树状图
  initGraph();
  addNodes();
});

</script>
<style>
.container {
  padding: 20px;
}

.config-area {
  width: 100%;
  margin-bottom: 20px;
}

.config-item {
  margin-bottom: 10px;
}

.config-item  .label {
  display: block;
  margin-left: 10px;
  margin-top: 5px;
  margin-right: 10px;
  width: 80px;
}

.button-area {
  margin-bottom: 20px;
  text-align: right;
}

.button-area button {
  margin-right: 10px;
}

.graph-container {
  border: 1px solid #ccc;
}
</style>